package apps

import (
	"news/pkg/apps/ctx"
	"news/pkg/models"
	"news/pkg/services"
	"news/pkg/types"
	"news/pkg/types/errors"
	"time"
)

func SearchNews(c *ctx.Context, form *types.SearchNewsForm) (interface{}, error) {
	query := services.QueryNews(c.DB(), form.Q)
	news := make([]types.GetNewsResp, 0)
	if err := query.Find(&news).Error; err != nil {
		return nil, errors.AutoDbErr(err)
	}
	return c.PageResult(query, form.Page(), form.PageSize(), &news)
}

func GetNewsById(c *ctx.Context, id models.Id) (interface{}, error) {
	news, err := services.GetNewsById(c.DB(), id)
	if err != nil {
		return nil, err
	}
	//阅读量+1
	newsInfo, err2 := services.AddReadCount(c.DB(), news)
	if err2 != nil {
		return nil, err2
	}
	return types.GetNewsResp{
		Id:        newsInfo.Id,
		CreatedAt: newsInfo.CreatedAt,
		Title:     newsInfo.Title,
		Label:     newsInfo.Label,
		UserId:    newsInfo.UserId,
		Username:  newsInfo.Username,
		State:     newsInfo.State,
		Url:       newsInfo.Url,
		Desc:      newsInfo.Desc,
		Content:   newsInfo.Content,
		ReadCount: newsInfo.ReadCount,
	}, nil
}
func DeleteNews(c *ctx.Context, form *types.DeleteNewsForm) (interface{}, error) {
	userInfo, err := services.GetUserById(c.DB(), c.MustUser().Id)
	if err != nil {
		return nil, err
	}
	if userInfo.Role != "admin" {
		return nil, errors.ErrPermDeny
	}
	deleteErr := services.DeleteNews(c.DB(), form.Ids)
	if deleteErr != nil {
		return nil, deleteErr
	}
	return nil, nil
}

func DeleteNewsById(c *ctx.Context, id models.Id) (interface{}, error) {
	news, err := services.GetNewsById(c.DB(), id)
	if err != nil {
		return nil, err
	}
	if c.MustUser().Id != models.Id(news.UserId) {
		return nil, errors.ErrPermDeny
	}
	deleteErr := services.DeleteNewsById(c.DB(), id)
	if deleteErr != nil {
		return nil, deleteErr
	}
	return types.DeleteNewsByIdResp{
		Id:     news.Id,
		UserId: models.Id(news.UserId),
		Title:  news.Title,
	}, nil
}

func CreateNews(c *ctx.Context, form *types.CreateNewsForm) (interface{}, error) {
	form.UserId = c.MustUser().Id
	form.Username = c.MustUser().Username
	news, err := services.CreateNews(c.DB(), form)
	if err != nil {
		return nil, err
	}
	return types.GetNewsResp{
		Id:        news.Id,
		CreatedAt: news.CreatedAt,
		NewsImg:   news.NewsImg,
		Title:     news.Title,
		Label:     news.Label,
		UserId:    news.UserId,
		Username:  news.Username,
		State:     news.State,
		Url:       news.Url,
		Desc:      news.Desc,
		Content:   news.Content,
		ReadCount: news.ReadCount,
	}, nil
}

func UpdateNewsById(c *ctx.Context, form *types.UpdateNewsForm) (interface{}, error) {
	news, err := services.GetNewsById(c.DB(), form.Id)
	if err != nil {
		return nil, err
	}
	if string(c.MustUser().Id) != news.UserId {
		return nil, errors.ErrPermDeny
	}
	updatedNews, updateErr := services.UpdateNews(c.DB(), form)
	if err != nil {
		return nil, updateErr
	}
	return updatedNews, nil
}

func UpdateStateByIds(c *ctx.Context, form *types.UpdateStateForm) (interface{}, error) {
	user, err := services.GetUserById(c.DB(), c.MustUser().Id)
	if err != nil {
		return nil, err
	}
	if user.Role != "admin" {
		return nil, errors.ErrPermDeny
	}
	_, updateErr := services.UpdateStateByIds(c.DB(), form)
	if updateErr != nil {
		return nil, updateErr
	}
	return nil, nil
}

func GetNewsByUserId(c *ctx.Context, form *types.GetNewsByUserIdForm) (interface{}, error) {
	query := services.GetNewsByUserId(c.DB(), form.UserId)
	news := make([]types.GetNewsResp, 0)
	if err := query.Find(&news).Error; err != nil {
		return nil, errors.AutoDbErr(err)
	}
	return c.PageResult(query, form.Page(), form.PageSize(), &news)
}

func GetNewsCountByType(c *ctx.Context, form *types.GetNewsCountByTypeForm) (interface{}, error) {
	counts, err := services.GetNewsCountByType(c.DB(), form.CreatedTime)
	if err != nil {
		return nil, err
	}
	return counts, nil
}

func GetNewsByState(c *ctx.Context, form *types.GetNewsByState) (interface{}, error) {
	news := make([]types.GetNewsResp, 0)
	query := services.GetNewsByState(c.DB(), form.State)
	if err := query.Find(&news).Error; err != nil {
		return nil, errors.AutoDbErr(err)
	}
	return c.PageResult(query, form.Page(), form.PageSize(), &news)
}

func GetNewsList(c *ctx.Context, form *types.GetNewsListForm) (interface{}, error) {
	news := make([]types.GetNewsResp, 0)
	query := services.GetNewsList(c.DB(), form.Q)
	if err := query.Find(&news).Error; err != nil {
		return nil, errors.AutoDbErr(err)
	}
	return c.PageResult(query, form.Page(), form.PageSize(), &news)
}

func GetWeekCount(c *ctx.Context) (interface{}, error) {
	var TDate [7]string
	var Count [7]int
	c.Logger()
	t := time.Now()
	currentTime := time.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, t.Location())
	for i := 0; i < 7; i++ {
		oldtime := currentTime.AddDate(0, 0, i-6)
		TDate[i] = oldtime.Format("01/02")
		Count[i] = services.GetDayNewsAddCount(c.DB(), oldtime.AddDate(0, 0, 1), oldtime)
	}
	return types.WeekNewsCountResp{
		Date:  TDate,
		Count: Count,
	}, nil
}
